package cn.jinbyte.web.aspect;

import cn.jinbyte.web.annotation.LoginLog;
import cn.jinbyte.web.config.LoginLogProperties;
import cn.jinbyte.web.dao.LoginLogDao;
import cn.jinbyte.web.model.LogRecord;
import cn.jinbyte.web.utils.helper.WebLogHelper;
import cn.jinbyte.web.utils.helper.WebRequestHelper;
import cn.jinbyte.web.utils.helper.WebResponseHelper;
import lombok.RequiredArgsConstructor;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Pointcut;

import java.time.Duration;
import java.time.Instant;

/**
 * 登录日志切面
 *
 * @author jinty
 */
@RequiredArgsConstructor
public class LoginLogAspect {

    private final LoginLogProperties properties;

    private final LoginLogDao logDao;

    /**
     * 登录日志切点
     */
    @Pointcut("@annotation(loginLog)")
    public void pointcut(LoginLog loginLog) {

    }

    /**
     * 登录日志切面环绕处理
     */
    @Around("pointcut(loginLog)")
    public Object around(ProceedingJoinPoint joinPoint, LoginLog loginLog) throws Throwable {
        Instant startTime = Instant.now();
        String errorMsg = null;
        Object result;
        try {
            result = joinPoint.proceed();
        } catch (Throwable ex) {
            errorMsg = ex.getMessage();
            throw ex;
        } finally {
            LogRecord logRecord = LogRecord.builder()
                    .timestamp(startTime)
                    .module("用户认证")
                    .domain(loginLog.userType() + "登录")
                    .request(WebLogHelper.logRequest(WebRequestHelper.getRequest(), null))
                    .accessUser(null) // todo
                    .response(WebLogHelper.logResponse(WebResponseHelper.getResponse(), null))
                    .timeTaken(Duration.between(startTime, Instant.now()))
                    .errorMsg(errorMsg)
                    .build();
            logDao.add(logRecord);
        }
        return result;
    }
}
